package com.miao.hong.fang.index;

import java.io.File;
import java.io.StringReader;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import org.apache.lucene.analysis.TokenStream;
import org.apache.lucene.analysis.standard.StandardAnalyzer;
import org.apache.lucene.document.Document;
import org.apache.lucene.queryParser.QueryParser;
import org.apache.lucene.search.BooleanClause;
import org.apache.lucene.search.BooleanQuery;
import org.apache.lucene.search.IndexSearcher;
import org.apache.lucene.search.ScoreDoc;
import org.apache.lucene.search.TopScoreDocCollector;
import org.apache.lucene.search.highlight.Highlighter;
import org.apache.lucene.search.highlight.QueryScorer;
import org.apache.lucene.search.highlight.SimpleFragmenter;
import org.apache.lucene.search.highlight.SimpleHTMLFormatter;
import org.apache.lucene.store.FSDirectory;
import org.apache.lucene.util.Version;
import org.apache.struts.action.ActionForm;
import org.apache.struts.action.ActionForward;
import org.apache.struts.action.ActionMapping;
import org.apache.struts.actions.DispatchAction;
import org.apache.struts.validator.DynaValidatorActionForm;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;

import com.miao.hong.fang.IConstants;
import com.miao.hong.fang.admin.service.AdminService;
import com.miao.hong.fang.course.CourseTO;
import com.miao.hong.fang.course.service.CourseService;
import com.miao.hong.fang.index.service.IndexService;
import com.miao.hong.fang.teacher.TeacherTO;
import com.miao.hong.fang.user.service.UserService;
import com.miao.hong.fang.util.ConfigProperties;
import com.miao.hong.fang.util.SpringBeansHolder;
import com.miao.hong.fang.util.Utils;
import com.miao.hong.fang.webservice.ipAddress.IpAddressSearchWebServiceStub;
import com.miao.hong.fang.webservice.weather.WeatherWebServiceStub;

public class IndexAction extends DispatchAction{

	private IndexService indexService = SpringBeansHolder.getInstance().getIndexService();
	private AdminService adminService = SpringBeansHolder.getInstance().getAdminService();
	private CourseService courseService = SpringBeansHolder.getInstance().getCourseService();
	private UserService userService = SpringBeansHolder.getInstance().getUserService();
	
	private static Log log = LogFactory.getLog(IndexAction.class);
	
	public ActionForward index(ActionMapping mapping, ActionForm form, HttpServletRequest request,
            HttpServletResponse response) throws Exception {
		
		//first get hot course
		List hotCouse = indexService.getHotCourse();
		request.setAttribute("hotCourse", Utils.getCellOfList(hotCouse, 7, IConstants.ORDER_TYPE_FRONT));
		
		//get course in city
		//String cityName = Utils.parseZhCN(request.getParameter("cityName"));  //BeiJing|ShangHai|ShenZhen
		String cityName = ConfigProperties.getInstance().getProperties("messages-default", "cityName", "beijing");  //BeiJing|ShangHai|ShenZhen
		String[] cityArr = cityName.split("\\|");
		
		List courseBJ = indexService.getCityCourse(cityArr[0]);		
		List courseShangHai = indexService.getCityCourse(cityArr[1]);
		List courseShenZhen = indexService.getCityCourse(cityArr[2]);
		request.setAttribute("courseBJ", courseBJ);
		request.setAttribute("courseShangHai", courseShangHai);
		request.setAttribute("courseShenZhen", courseShenZhen);
		
		//get first six teachers
		List result = adminService.searchTeacher(null, null, null).getList();
		List teacher = Utils.getCellOfList(result, 6, IConstants.ORDER_TYPE_FRONT);
		TeacherTO to = null;
		for (int i = 0; i < teacher.size(); i++) {
			 to = (TeacherTO) teacher.get(i);
			 String teacherImagePath = request.getContextPath() + "/images/teacher/" + to.getTeacherImageName();
			 to.setTeacherImagePath(teacherImagePath);
		}
		request.setAttribute("teacherList", teacher);
		
		//get recommended course
		List recommendedCourse = indexService.getRecommendedCourse();
		request.setAttribute("recommendedCourse", Utils.getCellOfList(recommendedCourse, 10, IConstants.ORDER_TYPE_FRONT));
		
		//second get hot course
		request.setAttribute("hotCourse2", Utils.getCellOfList(hotCouse, 10, IConstants.ORDER_TYPE_FRONT));
		
		//get first six category and corresponding courses
		Map<String, Object> map = new HashMap<String, Object>();
		List courseCategory = Utils.getCellOfList(courseService.getAllCourseCategory(), 6, IConstants.ORDER_TYPE_FRONT);
		List courseInCategory = null;
		for (int i = 0, j = courseCategory.size(); i < j; i++) {
			
			String category = (String) courseCategory.get(i);
			courseInCategory = indexService.getCourseByCategory(category);
			map.put(category, Utils.getCellOfList(courseInCategory, 6, IConstants.ORDER_TYPE_FRONT));
		}
		request.setAttribute("map", map);
		request.setAttribute("courseCategory", courseCategory);
		
		//log access info
		if(userService.getAccessInfo(request.getSession(false).getId()) == null) {
			userService.logAccessInfo(request.getSession(false).getId(), "visitor", request.getRemoteAddr());
		}
		
		//set login name if logined before
		Cookie[] cookies = request.getCookies();
		if(cookies != null) {
			for(Cookie cookie: cookies) {
				if("loginName".equals(cookie.getName())) {
					String loginName = cookie.getValue();
					request.setAttribute("loginName_Cookie", loginName);
					break;
				}
			}
		}
		
		//get the city by ip
//		if(request.getSession().getAttribute("userLocation") == null) {
//			String ip = request.getRemoteAddr();
//			
//			IpAddressSearchWebServiceStub stub = new IpAddressSearchWebServiceStub();
//			IpAddressSearchWebServiceStub.GetCountryCityByIp ip1 = new IpAddressSearchWebServiceStub.GetCountryCityByIp();
//			ip1.setTheIpAddress(ip);
//			IpAddressSearchWebServiceStub.GetCountryCityByIpResponse res = stub.getCountryCityByIp(ip1);
//			String[] s = res.getGetCountryCityByIpResult().getString();
//			
//			if(s != null && s.length>1) {
//				request.getSession().setAttribute("userLocation", s[1]);
//			}
//		}
		
		//get the weather
//		if(request.getSession().getAttribute("temperature") == null) {
//			WeatherWebServiceStub weatherStub = new WeatherWebServiceStub();
//			
//			WeatherWebServiceStub.GetWeatherbyCityName weatherCityName = new WeatherWebServiceStub.GetWeatherbyCityName();
//			weatherCityName.setTheCityName("苏州");
//			//weatherStub.getWeatherbyCityName(weatherCityName);
//			WeatherWebServiceStub.GetWeatherbyCityNameResponse weatherRep = weatherStub.getWeatherbyCityName(weatherCityName);
//			WeatherWebServiceStub.ArrayOfString weatherResult = weatherRep.getGetWeatherbyCityNameResult();
//			
//			if(weatherResult.getString() != null) {
//				String[] weather = weatherResult.getString();
//				request.getSession().setAttribute("temperature", weather[5]);
//				request.getSession().setAttribute("weather", weather[6].split(" ")[1]);
//			}
//		}
		
		return mapping.findForward("success");
	}

	public ActionForward search(ActionMapping mapping, ActionForm form, HttpServletRequest request,
            HttpServletResponse response) throws Exception{
		DynaValidatorActionForm dynaForm = (DynaValidatorActionForm) form;
		String searchText = dynaForm.getString("searchText");
		String[] criteriaArr = searchText.trim().split(" ");
		
		String indexPath = request.getSession().getServletContext().getRealPath("lucene_index");
		File file = new File(indexPath);
		IndexSearcher searcher = new IndexSearcher(FSDirectory.open(file));
		BooleanQuery booleanQuery = new BooleanQuery();
		
		QueryParser parser = null;
		StandardAnalyzer analyzer = new StandardAnalyzer(Version.LUCENE_30);
		for(int i = 0; i < criteriaArr.length; i++) {
			parser = new QueryParser(Version.LUCENE_30, "titleAndMainPointJoin", analyzer);
			booleanQuery.add(parser.parse(criteriaArr[i]), BooleanClause.Occur.MUST);
		}
		
		TopScoreDocCollector collector = TopScoreDocCollector.create(100, true);
		searcher.search(booleanQuery, collector);
		ScoreDoc[] hits = collector.topDocs().scoreDocs;
		
		List<CourseTO> list = new ArrayList<CourseTO>();
		CourseTO course = null;
		for (int i = 0; i < hits.length; i++) {
			Document hitDoc = searcher.doc(hits[i].doc);
			
			
			String courseTitle = hitDoc.get("courseTitle");
			SimpleHTMLFormatter simpleHTMLFormatter = new SimpleHTMLFormatter("<font color=\"red\">", "</font>");
			Highlighter highlighter = new Highlighter(simpleHTMLFormatter, new QueryScorer(booleanQuery));
			//highlighter.setTextFragmenter(new SimpleFragmenter(courseTitle.length()));
			highlighter.setTextFragmenter(new SimpleFragmenter(courseTitle.length() + 10));
			TokenStream tokenStream = analyzer.tokenStream("courseTitle", new StringReader(courseTitle));
			String highlighteText = highlighter.getBestFragment(tokenStream, courseTitle);
			
			
			course = new CourseTO();
			course.setCourseId(hitDoc.get("id"));
			course.setCourseTitle(highlighteText);
			
			course.setCourseCategory(hitDoc.get("courseCategory"));
			course.setCourseCity(hitDoc.get("courseCity"));
			course.setCourseStartTime(Utils.stringToTimestamp(hitDoc.get("courseStartTimeAsStr"), IConstants.COURSE_START_TIME_FORMAT));
			course.setCourseMainPoint(hitDoc.get("courseMainPoint"));
			
			list.add(course);
		}
		request.setAttribute("searchResult", list);
		return mapping.findForward("success");
	}
}
